import type { ConnectUISettings, ConnectionResponseSuccess } from '@nangohq/types';

export type AuthErrorType =
    | 'missing_auth_token'
    | 'blocked_by_browser'
    | 'invalid_host_url'
    | 'missing_credentials'
    | 'window_closed'
    | 'connection_test_failed'
    | 'missing_connect_session_token'
    | 'connection_validation_failed'
    | 'resource_capped'
    | 'unknown_error';

export type AuthResult = ConnectionResponseSuccess;
export type AuthSuccess = AuthResult; // alias for backward compatibility

export type AuthOptions = {
    detectClosedAuthWindow?: boolean; // If true, `nango.auth()` would fail if the login window is closed before the authorization flow is completed
} & (ConnectionConfig | OAuthCredentialsOverride);

export type ErrorHandler = (errorType: AuthErrorType, errorDesc: string) => void;

export interface ConnectionConfig {
    params?: Record<string, string>;
    hmac?: string;
    user_scope?: string[];
    authorization_params?: Record<string, string | undefined>;
    installation?: 'outbound';
    credentials?:
        | OAuthCredentialsOverride
        | BasicApiCredentials
        | ApiKeyCredentials
        | AppStoreCredentials
        | TBACredentials
        | JwtCredentials
        | TwoStepCredentials
        | OAuth2ClientCredentials
        | SignatureCredentials;
}

export interface OAuthCredentialsOverride {
    oauth_client_id_override: string;
    oauth_client_secret_override: string;
}

export interface BasicApiCredentials {
    username?: string;
    password?: string;
}

export interface ApiKeyCredentials {
    apiKey?: string;
}

export interface AppStoreCredentials {
    privateKeyId: string;
    issuerId: string;
    privateKey: string;
    scope?: string[];
}

export interface TBACredentials {
    token_id: string;
    token_secret: string;
    oauth_client_id_override?: string;
    oauth_client_secret_override?: string;
}

export interface JwtCredentials {
    type?: 'JWT';
    [key: string]: any;
}

export interface OAuth2ClientCredentials {
    client_id: string;
    client_secret: string;
    client_certificate?: string;
    client_private_key?: string;
}

export interface BillCredentials {
    username: string;
    password: string;
    organization_id: string;
    dev_key: string;
}

export interface TwoStepCredentials {
    type: 'TWO_STEP';
    [key: string]: any;
}

export interface SignatureCredentials {
    type: 'SIGNATURE';
    username: string;
    password: string;
}

// This one is sent by parent only
export interface ConnectUIEventToken {
    type: 'session_token';
    sessionToken: string;
}

export interface ConnectUIEventReady {
    type: 'ready';
}

export interface ConnectUIEventClose {
    type: 'close';
}

export interface ConnectUIEventConnect {
    type: 'connect';
    payload: AuthResult;
}

export interface ConnectUIEventError {
    type: 'error';
    payload: {
        errorType: AuthErrorType;
        errorMessage: string;
    };
}

export interface ConnectUIEventSettingsChanged {
    type: 'settings_changed';
    payload: ConnectUISettings;
}

export type ConnectUIEvent = ConnectUIEventReady | ConnectUIEventClose | ConnectUIEventConnect | ConnectUIEventError | ConnectUIEventSettingsChanged;
